#pragma once

#include "../io.h"

namespace sfc::fs {

using io::Error;

static constexpr auto MAX_PATH = 256;

struct Path : Str {
  using Base = Str;

  Path(Str s) noexcept : Str{s} {}

  auto parent() const -> Path;
  auto file_name() const -> Str;
  auto file_stem() const -> Str;
  auto extension() const -> Str;

  auto exists() const -> bool;
  auto is_file() const -> bool;
  auto is_dir() const -> bool;

  auto to_path_buf() const -> struct PathBuf;
};

struct PathBuf : protected String {
  using Base = String;

  explicit PathBuf(String&& other) noexcept;
  static auto from(Str s) -> PathBuf;

  auto as_path() const -> Path;
  auto exists() const -> bool;
  auto is_file() const -> bool;
  auto is_dir() const -> bool;

  auto parent() const -> Path;
  auto file_name() const -> Str;
  auto file_stem() const -> Str;
  auto extension() const -> Str;

  void push(Path p);
  void pop();
  void set_file_name(Str new_name);
  void set_extension(Str new_ext);
};

struct Metadata {
  u64 _len;
  u32 _mod;

  auto len() const -> u64;
  auto is_dir() const -> bool;
  auto is_file() const -> bool;
  auto is_link() const -> bool;

  static auto from_link(Path path) -> Metadata;
  static auto from_path(Path path) -> Metadata;
};

void create_dir(Path p);
void remove_file(Path p);
void remove_dir(Path p);
void rename(Path from, Path to);

}  // namespace sfc::fs
